home *** CD-ROM | disk | FTP | other *** search
- /*
- Kermit Vt100 emulator code modified by Jerry LeVan
- to fit the MiniTerm project.
- Date Sept 7,1987
- Changes: Modified the cursor control routines
- Added Control character Display
- Added Line Drawing Graphics Support
- */
- /* By Frank on June 20 - Add parity to all outbound chars using software */
- /* Also, ignore DEL (0177) characters on input. */
- /* By Bill on May 29 - Add Key set translation */
- /* By WBC3 on Apr 24 - Add ^^, ^@ and ^_. Also use Pascal strings for */
- /* output in the terminal emulator */
- /* By WBC3 on Apr 23 - Add query terminal and be more fastidious about */
- /* ignoring sequences we don't know about */
- /* By WBC3 on Apr 22 - Fix tab stops to conform to the rest of the world! */
- /* By Bill on Apr 21 - Fix immediate echo problems. */
- /* do less cursor_erase, cursor_draw stuff */
-
- /*
- * vt100.c
- *
- * Module of MiniTerm: contains most code for the terminal simulation
- * routine.
- */
-
- #include <types.h>
- #include <Quickdraw.h>
- #include <Windows.h>
- #include <Fonts.h>
- #include <Menus.h>
- #include <Events.h>
- #include <serial.h>
- #include <OSUtils.h>
-
- #define tickCount *(long *)0x16a
- #define caretTime *(long *)0x2f4
-
- #define False 0
- #define True 1
- #define FALSE 0
- #define TRUE 1
- #define MAXLIN 24
- #define MAXCOL 80
- #define LINEHEIGHT 11
- #define CHARWIDTH 6
- #define TOPMARGIN 3 /* Terminal display constants */
- #define BOTTOMMARGIN (LINEHEIGHT * MAXLIN + TOPMARGIN)
- #define LEFTMARGIN 3
- #define RIGHTMARGIN (CHARWIDTH * MAXCOL + LEFTMARGIN)
- #define LINEADJ 3 /* Amount of char below base line */
-
- /* cursor variables */
- static char cursorActive;
- static Boolean cursorInverted=false ; /* true means inverted pen rect */
- static long cursorTime;
- static Rect penRect;
- static FontInfo fontstuff;
- Boolean useBlockCursor = false;
- Boolean blink=true; /* true means blink the cursor */
- Boolean invisible = false;
-
- /* output character handling */
-
- unsigned char obuf[2] = {1,0}; /* single char output buffer */
-
- /* Tab settings */
-
- #define NUMTABS 9
-
- short tabstops[NUMTABS] = {8,16,24,32,40,48,56,64,72};
-
- int Invert=FALSE, /* Flag for Inverted terminal mode */
- insert=FALSE,
- topmargin=TOPMARGIN, /* Edges of adjustable window */
- bottommargin=BOTTOMMARGIN,
- textstyle=0,
- autowrap=TRUE; /* Autowrap on by default */
-
- char *querystring="\033[?6c"; /* Answer we are a VT102 */
-
- short scrollrect[] = { TOPMARGIN, LEFTMARGIN, BOTTOMMARGIN, RIGHTMARGIN };
-
- RgnHandle dumptr; /* Dummy ptr to satisfy scrollbits */
-
- /* Screen book keeping variables */
-
- char scr[MAXLIN][MAXCOL+1]; /* Characters on the screen */
- short nxtlin[MAXLIN], toplin, botlin; /* Linked list of lines */
- int curlin, curcol, abslin; /* Cursor position */
- int savcol, savlin; /* Cursor save variables */
- int scrtop, scrbot; /* Absolute scrolling region bounds */
-
- /* Stuff for escape character processing */
-
- #define CF_OUTC 0 /* Just output the char */
- #define CF_SESC 1 /* In a single char escape seq */
- #define CF_MESC 2 /* In a multi char '[' escape seq */
- #define CF_TOSS 3 /* Toss this char */
-
- char prvchr, numone[6], numtwo[6], *numptr;
- int num1, num2, charflg=CF_OUTC;
-
- Boolean use_ascii = true; /* false means use graphics characters */
- Boolean keypad_app = false; /* false means don't send escape sequences */
- extern Boolean interpret_control; /* false means show control character */
-
- extern short sOut; /* refnum of output port */
- typedef int (*PFI) ();
-
- /* Terminal function declarations. */
-
- int tab(), back_space(), carriage_return(), line_feed(), bell(), escape_seq(),
- text_mode(), clear_line(), erase_display(), cursor_position(), cursor_up(),
- cursor_down(), cursor_right(), cursor_left(), cursor_save(),
- cursor_restore(), set_scroll_region(), reverse_line_feed(), dummy(),
- delete_char(), insert_mode(), end_insert_mode(), insert_line(),
- delete_line(), query_terminal(), multi_char(), toss_char(),
- set_ascii(),set_graphics(),set_keypad(),reset_keypad(),cursor_attributes();
-
- /* Terminal control character function command table. */
-
- #define MINSINGCMDS 000
- #define MAXSINGCMDS 037
-
- PFI controltable[MAXSINGCMDS-MINSINGCMDS+1] =
- {
- dummy, /* 0 */
- dummy, /* 1 */
- dummy, /* 2 */
- dummy, /* 3 */
- dummy, /* 4 */
- dummy, /* 5 */
- dummy, /* 6 */
- bell, /* 7 */
- back_space, /* 10 */
- tab, /* 11 */
- line_feed, /* 12 */
- line_feed, /* 13 (Vertical tab) */
- line_feed, /* 14 (Form feed) */
- carriage_return, /* 15 */
- set_graphics, /* 16 'N'*/
- set_ascii, /* 17 */
- dummy, /* 20 */
- dummy, /* 21 */
- dummy, /* 22 */
- dummy, /* 23 */
- dummy, /* 24 */
- dummy, /* 25 */
- dummy, /* 26 */
- dummy, /* 27 */
- dummy, /* 30 */
- dummy, /* 31 */
- dummy, /* 32 */
- escape_seq, /* 33 (Escape) */
- dummy, /* 34 */
- dummy, /* 35 */
- dummy, /* 36 */
- dummy /* 37 */
- };
-
- #define MINSINGESCS 0040
- #define MAXSINGESCS 0137
-
- PFI singescapetable[MAXSINGESCS-MINSINGESCS+1] =
- {
- dummy, /* 40 */
- dummy, /* 41 */
- dummy, /* 42 */
- toss_char, /* 43 '#' */
- dummy, /* 44 */
- dummy, /* 45 */
- dummy, /* 46 */
- dummy, /* 47 */
- toss_char, /* 50 '(' */
- toss_char, /* 51 ')' */
- dummy, /* 52 */
- dummy, /* 53 */
- dummy, /* 54 */
- dummy, /* 55 */
- dummy, /* 56 */
- dummy, /* 57 */
- set_graphics, /* 60 '0' */
- dummy, /* 61 */
- dummy, /* 62 */
- dummy, /* 63 */
- dummy, /* 64 */
- dummy, /* 65 */
- dummy, /* 66 */
- cursor_save, /* 67 '7' */
- cursor_restore, /* 70 '8' */
- dummy, /* 71 */
- dummy, /* 72 */
- dummy, /* 73 */
- dummy, /* 74 '<' */
- set_keypad, /* 75 '=' */
- reset_keypad, /* 76 '>' */
- dummy, /* 77 */
- dummy, /* 100 */
- dummy, /* 101 */
- set_ascii, /* 102 'B' */
- dummy, /* 103 */
- line_feed, /* 104 'D' */
- dummy, /* 105 'E' */
- dummy, /* 106 */
- dummy, /* 107 */
- dummy, /* 110 */
- dummy, /* 111 */
- dummy, /* 112 */
- dummy, /* 113 */
- dummy, /* 114 */
- reverse_line_feed, /* 115 'M' */
- dummy, /* 116 */
- dummy, /* 117 */
- dummy, /* 120 */
- dummy, /* 121 */
- dummy, /* 122 */
- dummy, /* 123 */
- dummy, /* 124 */
- dummy, /* 125 */
- dummy, /* 126 */
- dummy, /* 127 */
- dummy, /* 130 */
- dummy, /* 131 */
- query_terminal, /* 132 'Z' */
- multi_char, /* 133 '[' */
- dummy, /* 134 */
- dummy, /* 135 */
- dummy, /* 136 */
- dummy /* 137 */
- };
-
- /* Terminal escape sequence function command table */
-
- #define MINMULTESCS 0100
- #define MAXMULTESCS 0177
-
- PFI escapetable[MAXMULTESCS-MINMULTESCS+1] =
- {
- dummy, /* 100 */
- cursor_up, /* 101 'A' */
- cursor_down, /* 102 'B' */
- cursor_right, /* 103 'C' */
- cursor_left, /* 104 'D' */
- dummy, /* 105 */
- dummy, /* 106 */
- dummy, /* 107 */
- cursor_position, /* 110 'H' */
- dummy, /* 111 */
- erase_display, /* 112 'J' */
- clear_line, /* 113 'K' */
- insert_line, /* 114 'L' */
- delete_line, /* 115 'M' */
- dummy, /* 116 */
- dummy, /* 117 */
- delete_char, /* 120 'P' */
- dummy, /* 121 */
- dummy, /* 122 */
- dummy, /* 123 */
- dummy, /* 124 */
- dummy, /* 125 */
- dummy, /* 126 */
- dummy, /* 127 */
- dummy, /* 130 */
- dummy, /* 131 */
- dummy, /* 132 */
- dummy, /* 133 */
- dummy, /* 134 */
- dummy, /* 135 */
- dummy, /* 136 */
- dummy, /* 137 */
- dummy, /* 140 */
- dummy, /* 141 */
- dummy, /* 142 */
- query_terminal, /* 143 'c' */
- dummy, /* 144 */
- dummy, /* 145 */
- cursor_position, /* 146 'f' */
- dummy, /* 147 */
- insert_mode, /* 150 'h' */
- dummy, /* 151 */
- dummy, /* 152 */
- dummy, /* 153 */
- end_insert_mode, /* 154 'l' */
- text_mode, /* 155 'm' */
- dummy, /* 156 */
- dummy, /* 157 */
- dummy, /* 160 */
- dummy, /* 161 */
- set_scroll_region, /* 162 'r'*/
- dummy, /* 163 */
- dummy, /* 164 */
- dummy, /* 165 */
- cursor_attributes, /* 166 'v'*/
- dummy, /* 167 */
- dummy, /* 170 */
- dummy, /* 171 */
- dummy, /* 172 */
- dummy, /* 173 */
- dummy, /* 174 */
- dummy, /* 175 */
- dummy, /* 176 */
- dummy /* 177 */
- };
- /**********************************************************************/
- /*
- The following routine returns true if pacing is turned on and
- the last nonwhite character on the current line is the pacing character
- */
- Boolean OKToSendChar(theChar,pacing,refNum,inprog)
- char theChar; /* the pacing character */
- Boolean pacing; /* true -> do pacing */
- short refNum; /* channel for modem */
- Boolean *inprog; /* true means a line is being sent */
-
- { short tmp; /* local index */
- SerStaRec statRec; /* for checking if we are xoff'ed */
-
- SerStatus(refNum,&statRec); /* check modem */
-
- if (statRec.xOffHold) return false; /* we are in a xoff state */
-
- if(!pacing) return true; /* easy case */
-
- if (*inprog) return true; /* a CR will set inprog to false */
-
- for(tmp=0;tmp < curcol;tmp++) /* scan line looking for pace character */
- if (scr[curlin][tmp] == theChar) {
- *inprog = true; /* starting a new line */
- return true; /* gotit */
- }
- return false; /* nothing was on the line */
-
- }
-
- /**********************************************************************/
-
- static int strlen(s)
- char *s;
- { int i;
- i=0;
- while(*s++)i++;
- return i;
- }
- /* cursor stuff */
- /* for vertical cursor use this */
- void oldgetPenRect(r) /* returns address of rect to invert */
- Rect *r;
- { Point pt; /* for pen cordinates */
- GetPen(&pt);
- r->top = pt.v - fontstuff.ascent;
- r->left = /*(pt.h==LEFTMARGIN)?pt.h-1:*/ pt.h; /* offset one pixel */
- r->bottom = pt.v +fontstuff.descent;
- r->right = /*(pt.h==LEFTMARGIN)?pt.h:*/ pt.h + 1; /* skinny */
- }
- void getPenRect(r)
- Rect *r;
- { Point pt;
- GetPen(&pt);
- r->top = useBlockCursor ? pt.v - fontstuff.ascent + 1: pt.v;
- r->bottom = pt.v + fontstuff.descent;
- r->left = pt.h;
- r->right = pt.h + fontstuff.widMax ;
- }
- void docursor()
- { if(invisible) return;
- if (!blink) return;
- if (cursorActive)
- if(cursorTime < tickCount )
- { cursorTime += caretTime;
- getPenRect(&penRect);
- InvertRect(&penRect);
- cursorInverted = !cursorInverted; /* change state */
- }
- }
-
- void start_cursor()
- { if(invisible) return;
- cursorActive = True;
- cursorTime = (tickCount) + (caretTime);
- /* cursorInverted = false; */
- if(!cursorInverted){
- getPenRect(&penRect); InvertRect(&penRect);
- cursorInverted =true;}
- }
-
- void stop_cursor()
- { if (invisible) return;
- cursorActive = False;
- if (cursorInverted) {
- getPenRect(&penRect); InvertRect(&penRect);
- cursorInverted =false;
- }
- }
-
- /**********************************************************************/
-
- /* Connect support routines */
-
- InitPage()
- { short theNum;
-
- dumptr = (RgnHandle)NewRgn();
- PenMode(patXor);
- GetFNum("vt100",&theNum);
- if(theNum)
- TextFont(theNum); /* keep it simple */
- else TextFont(monaco);
- TextSize(9);
- GetFontInfo(&fontstuff);
- init_term(); /* Set up some terminal variables */
- clear_screen(); /* Clear the screen */
- home_cursor(); /* Go to the upper left */
- cursor_save(); /* Save this position */
- cursorInverted = false;
- start_cursor();
- }
-
-
-
- /* writeps - write a pascal form string to the serial port.
- *
- */
-
- writeps(s)
- char *s;
- {
- long wcnt, w2;
- int err; char *s2;
-
- w2 = wcnt = *s++; /* get count */
- err = FSWrite(sOut,&wcnt,s); /* write the characters */
- return;
- }
-
- /* getindstr - given an indirect (or is it indexed) string and integer
- * n, return the pointer to the Nth substring.
- *
- * Indirect strings have the count of substrings in the first byte and
- * each string follows with a length byte and a body.
- *
- * Substrings are referenced by 1..N
- *
- */
-
- char *getindstr(indstr,n)
- char *indstr;
- {
- register char *ip = indstr;
- int i;
-
- if (n > *ip++) /* too large? */
- return(""); /* yes, return empty pascal string */
-
- for (i=1; i < n; i++) /* scan until we hit the Nth */
- ip += (*ip)+1; /* move to next substring */
-
- return(ip); /* return ptr to it */
- }
-
-
- char outbuf[MAXCOL+1];
- int outcnt=0, outcol;
-
- flushbuf()
- {
- Rect r;
- Boolean cursorWasActive;
-
- if (outcnt == 0) return; /* Nothing to flush */
-
- if(cursorWasActive = cursorActive) stop_cursor();
-
- /* Erase a hole large enough for outcnt chars */
-
- makerect(&r,abslin,outcol,1,outcnt);
-
- if (Invert) FillRect(&r,qd.black);
- else EraseRect(&r);
-
- outbuf[outcnt] = '\0'; /* Terminate the string */
- DrawString(outbuf); /* Output the string */
- if(cursorWasActive)start_cursor();
- outcnt = 0; /* Say no more chars to output */
- }
-
- buf_char(c)
- char c;
- {
- if (outcnt == 0) outcol = curcol; /* No chars in buffer, init column */
- if(outcnt == MAXCOL){ SysBeep(3); return; } /* don't overflow buffer */
- outbuf[outcnt++] = c; /* Put in the buffer to output later */
- }
-
- /*
- * put_ch:
- * Draws character and updates buffer
- */
-
- void Put_Char(c)
- char c;
- {
- PFI funp, lookup();
-
- c &= 0177;
- stop_cursor();
- switch (charflg)
- {
- case CF_OUTC: /* Just output the char */
- drawAChar(c);
- break;
-
- case CF_SESC: /* In a single char escape seq */
- if(c == '(') break; /* wait for '0' or 'B' */
- charflg = CF_OUTC; /* Reset flag to simple outputting */
- if(funp=lookup(c,singescapetable,MINSINGESCS,MAXSINGESCS))
- (*funp)(); /* Do escape sequence function */
- break;
-
- case CF_MESC: /* Multichar escape sequence */
- if (c >= 0x20 && c < 0x40) /* Deal with the modifiers */
- {
- if (c >= '<' && c <= '?') prvchr = c; /* Handle priv char */
- else if ((c >= '0' && c <= '9') || c == '-' || c == '+')
- {
- *numptr++ = c; /* Add the char to the num */
- *numptr = '\0'; /* Terminate the string */
- }
- else if (c == ';') numptr = numtwo; /* Go to next number */
- }
- else /* End of sequence */
- {
- if (funp=lookup(c,escapetable,MINMULTESCS,MAXMULTESCS))
- {
- StringToNum(numone,&num1); /* Translate the numbers */
- StringToNum(numtwo,&num2);
- (*funp)(); /* Do the escape sequence function */
- }
- charflg = CF_OUTC; /* Back to simple outputting */
- }
- break;
-
- case CF_TOSS: /* Ignore this char */
- charflg = CF_OUTC; /* Reset flag */
- break;
- }
- start_cursor();
- }
-
- /*
- * Routine makerect
- *
- * Make a rectangle in r starting on line lin and column col extending
- * numlin lines and numcol characters.
- *
- */
-
- makerect(r,lin,col,numlin,numcol)
- Rect *r;
- int lin, col, numlin, numcol;
- {
- r->top = lin * LINEHEIGHT + TOPMARGIN;
- r->left = col * CHARWIDTH + LEFTMARGIN;
- r->bottom = r->top + numlin * LINEHEIGHT;
- r->right = r->left + numcol * CHARWIDTH;
- }
-
- /*
- * Lookup:
- * Lookup a given character in the apropriate character table, and
- * return a pointer to the appropriate function, if it exists.
- */
-
- PFI
- lookup(index,table,min,max)
- char index;
- PFI table[];
- int min, max;
- {
- if (index > max || index < min)
- return((PFI) NULL); /* Don't index out of range */
- return(table[index-min]);
- }
-
-
- /*
- * Flushio:
- * Initialize some communications constants, and clear screen and
- * character buffers.
- */
-
- flushio()
- {
- }
-
-
- /* sendbreak - sends a break across the communictions line.
- *
- * The argument is in units of approximately 0.05 seconds (or 50
- * milliseconds). To send a break of duration 250 milliseconds the
- * argument would be 5; a break of duration 3.5 seconds would be (umm,
- * lets see now) 70.
- *
- */
-
- sendbreak(msunit)
- {
- int finalticks;
-
-
- }
-
- drawAChar(chr)
- unsigned char chr;
- {
- PFI funp;
- Boolean cursorWasActive;
-
- if(cursorWasActive = cursorActive)stop_cursor();
-
- /* If it's a control char, do the apropriate function. */
- if ((chr < (unsigned char)' ') && interpret_control) /* Is it a control character */
- {
- flushbuf();
- if (funp=lookup(chr,controltable,MINSINGCMDS,MAXSINGCMDS)) (*funp)();
- }
- else if (chr < (unsigned char)0177) /* Handle graphic characters */
- {
- if(!use_ascii)
- if((chr >= (unsigned char)0137) && (chr <= (unsigned char)0176)) /* if in graphics mode */
- chr += 0200; /* offset to high ascii */
-
- if (chr < (unsigned char)0040) /* if a control char */
- if(!interpret_control) chr += 0200;
-
- if (curcol >= MAXCOL) /* Are we about to wrap around? */
- {
- if (autowrap) /* If autowrap indicated wrap */
- {
- flushbuf();
- carriage_return();
- line_feed();
- }
- else
- {
- back_space(); /* Otherwise just overwrite */
- outcnt--; /* Overwrite buffered chars too */
- }
- }
- if (insert) /* Insert mode? */
- {
- insert_char(); /* Open hole for char if requested */
- erase_char(); /* Erase the old char */
- DrawChar(chr);
- }
- else buf_char(chr); /* Otherwise just buffer the char */
- scr[curlin][curcol++] = chr;
- }
- if(cursorWasActive)start_cursor();
- }
-
- void drawCString(strptr)
- char * strptr;
- { char ch;
- while(ch=*strptr++)drawAChar(ch);
- }
-
- void drawPString(strptr)
- char *strptr;
- { short i;
- for(i=1;i<=strptr[0];i++)drawAChar(strptr[i]);
- }
-
-
- /*
- * Control character functions:
- * Each of the following allow the mac to simulate
- * the behavior of a terminal when given the proper
- * control character.
- */
-
- back_space()
- {
- if (curcol > 0) relmove(-1,0);
- }
-
- erase_char()
- {
- Rect r;
-
- scr[curlin][curcol] = ' '; /* Erase char for update */
- makerect(&r,abslin,curcol,1,1); /* One char by one line */
-
- if (Invert) FillRect(&r,qd.black);
- else EraseRect(&r);
- }
-
- tab()
- {
- int i;
-
- for (i=0; i<NUMTABS; i++)
- {
- if (tabstops[i] > curcol)
- {
- absmove(tabstops[i],abslin);
- return;
- }
- }
- }
-
- line_feed()
- {
- int tbot, ttop, tlout;
-
- if (curlin == scrbot)
- {
- ScrollRect((Rect *) scrollrect,0,-LINEHEIGHT,dumptr);
- SetEmptyRgn(dumptr);
- zeroline(scrtop);
- tbot = scrbot;
- ttop = scrtop;
- tlout = nxtlin[scrbot];
- nxtlin[scrbot] = scrtop;
- scrbot = scrtop;
- scrtop = nxtlin[scrtop];
- if (ttop == toplin) toplin = scrtop;
- else nxtlin[fndprv(ttop)] = scrtop;
- if (tbot == botlin)
- {
- botlin = scrbot;
- nxtlin[botlin] = -1;
- }
- else nxtlin[scrbot] = tlout;
- curlin = scrbot;
- }
- else relmove(0,1);
- }
-
- reverse_line_feed()
- {
- int tbot, ttop, tlout;
-
- if (curlin == scrtop)
- {
- ScrollRect((Rect *) scrollrect,0,LINEHEIGHT,dumptr);
- SetEmptyRgn(dumptr);
- zeroline(scrbot);
- tbot = scrbot;
- ttop = scrtop;
- tlout = nxtlin[scrbot];
- nxtlin[scrbot] = scrtop;
- scrtop = scrbot;
- scrbot = fndprv(scrbot);
- if (ttop == toplin) toplin = scrtop;
- else nxtlin[fndprv(ttop)] = scrtop;
- if (tbot == botlin)
- {
- botlin = scrbot;
- nxtlin[botlin] = -1;
- }
- else nxtlin[scrbot] = tlout;
- curlin = scrtop;
- }
- else relmove(0,-1);
- }
-
- carriage_return()
- {
- absmove(0,abslin);
- }
-
- clear_screen()
- {
- register int i;
- Rect r;
- GrafPtr thisPortptr;
-
- /*
- makerect(&r,0,0,MAXLIN,MAXCOL);
- EraseRect(&r);
- */
- GetPort(&thisPortptr);
- EraseRect(&thisPortptr->portRect);
-
- for (i=0; i<MAXLIN; i++) zeroline(i); /* Clear up the update records */
- }
-
- home_cursor()
- {
- absmove(0,0);
- }
-
- bell()
- {
- SysBeep(3);
- }
-
- escape_seq()
- {
- charflg = CF_SESC; /* Say we are in an escape sequence */
- }
-
- clear_line()
- {
- int i;
- Rect r;
-
- switch (num1)
- {
- case 0: /* Clear: here to the right */
- makerect(&r,abslin,curcol,1,MAXCOL-curcol);
- for (i=curcol; i<MAXCOL; i++) scr[curlin][i] = ' ';
- break;
-
- case 1: /* Clear: left to here */
- makerect(&r,abslin,0,1,curcol+1);
- for (i=0; i<=curcol; i++) scr[curlin][i] = ' ';
- break;
-
- case 2: /* Clear: entire line */
- makerect(&r,abslin,0,1,MAXCOL);
- zeroline(curlin);
- break;
- }
- EraseRect(&r);
- }
-
- erase_display()
- {
- int i;
- Rect r;
-
- switch (num1)
- {
- case 0:
- clear_line(); /* Same num1 causes correct clear */
- makerect(&r,abslin+1,0,MAXLIN-abslin,MAXCOL);
- EraseRect(&r);
- for (i=abslin+1; i<MAXLIN; i++) zeroline(fndrel(i));
- break;
-
- case 1:
- clear_line(); /* Same num1 causes correct clear */
- makerect(&r,0,0,abslin,MAXCOL);
- EraseRect(&r);
- for (i=0; i<abslin; i++) zeroline(fndrel(i));
- break;
-
- case 2:
- clear_screen();
- break;
- }
- }
-
- /**** All cursor moves need to check that they don't go beyond the margins */
-
- cursor_right()
- {
- if (num1 == 0) num1 = 1;
- relmove(num1,0);
- }
-
- cursor_left()
- {
- if (num1 == 0) num1 = 1;
- relmove(-num1,0);
- }
-
- cursor_up()
- {
- if (num1 == 0) num1 = 1;
- relmove(0,-num1);
- }
-
- cursor_down()
- {
- if (num1 == 0) num1 = 1;
- relmove(0,num1);
- }
-
- cursor_position()
- {
- if (--num1 < 0) num1 = 0;
- if (--num2 < 0) num2 = 0;
-
- absmove(num2,num1);
- }
-
- cursor_save()
- {
- savcol = curcol; /* Save the current line and column */
- savlin = abslin;
- }
-
- cursor_restore()
- {
- absmove(savcol,savlin); /* Move to the old cursor position */
- }
-
- cursor_draw()
- {
- Line(CHARWIDTH,0); /* Draw cursor */
- }
-
- cursor_erase()
- {
- Line(-CHARWIDTH,0); /* Erase cursor */
- }
-
- set_scroll_region()
- {
- if (--num1 < 0) num1 = 0; /* Make top of line (prev line) */
- if (num2 == 0) num2 = 24; /* Zero means entire screen */
-
- topmargin = scrollrect[0] = (num1 * LINEHEIGHT) + TOPMARGIN;
- bottommargin = scrollrect[2] = (num2 * LINEHEIGHT) + TOPMARGIN;
-
- scrtop = fndrel(num1);
- scrbot = fndrel(num2-1);
-
- home_cursor(); /* We're supposed to home it! */
- }
-
-
- text_mode() /**** */
- {
- switch(num1)
- {
- case 0:
- Invert=FALSE;
- textstyle=0;
- TextFace(0);
- TextMode(srcOr);
- TextSize(9);
- break;
-
- case 1:
- textstyle +=bold;
- TextFace(textstyle);
- TextSize(8); /* shrink a little */
- break;
-
- case 4:
- textstyle+=underline;
- TextFace(textstyle);
- TextSize(9);
- break;
-
- case 7:
- Invert=TRUE;
- TextMode(srcBic);
- TextSize(9);
- break;
-
- case 22:
- if (textstyle >= bold)
- {
- TextFace(textstyle-bold);
- textstyle -= bold;
- }
- break;
-
- case 24:
- if (textstyle >= underline)
- {
- TextFace(textstyle-underline);
- textstyle -= underline;
- }
- break;
-
- case 27:
- Invert = FALSE;
- TextMode(srcOr);
- break;
- }
- }
-
- /**** NYI */
- insert_line()
- {
- Rect r;
-
- if (num1 == 0) num1 = 1;
-
- makerect(&r,abslin,0,0,MAXCOL);
- r.bottom = bottommargin; /* Just do this for now */
-
- if (num1 > fndabs(scrbot) - abslin)
- num1 = fndabs(scrbot) - abslin;
-
- ScrollRect(&r,0,num1*LINEHEIGHT,dumptr);
- SetEmptyRgn(dumptr);
- /* Do the book keeping!!! */
- }
-
- delete_line()
- {
- Rect r;
-
- if (num1 == 0) num1 = 1;
-
- makerect(&r,abslin,0,0,MAXCOL);
- r.bottom = bottommargin; /* Just do this for now */
-
- if (num1 > fndabs(scrbot) - abslin)
- num1 = fndabs(scrbot) - abslin;
-
- ScrollRect(&r,0,-num1*LINEHEIGHT,dumptr);
- SetEmptyRgn(dumptr);
- /* Do the book keeping!!! */
- }
-
- delete_char()
- {
- int i;
- Rect r;
-
- if (num1 == 0) num1 = 1;
-
- makerect(&r,abslin,curcol,1,MAXCOL-curcol);
-
- if(num1 > MAXCOL - curcol - 1) num1 = MAXCOL - curcol - 1;
-
- ScrollRect(&r,-CHARWIDTH*num1,0,dumptr); /* Scroll em out */
- SetEmptyRgn(dumptr);
-
- /* Shift em down */
-
- for (i=curcol; i<MAXCOL-num1; i++) scr[abslin][i] = scr[abslin][i+num1];
- while (i < MAXCOL) scr[abslin][i++] = ' '; /* Fill in holes with spaces */
- }
-
- insert_char()
- {
- int i;
- Rect r;
-
- makerect(&r,abslin,curcol,1,MAXCOL-curcol);
-
- ScrollRect(&r,CHARWIDTH,0,dumptr);
- SetEmptyRgn(dumptr);
-
- /* Shift em up */
-
- for (i=MAXCOL-1; i>curcol+1; i--) scr[abslin][i-1] = scr[abslin][i];
- scr[abslin][curcol] = ' ';
- }
-
- insert_mode()
- {
- if (prvchr == '?') return; /* Don't deal with these calls */
- if (num1 == 4) insert = TRUE;
- }
-
- end_insert_mode()
- {
- if (prvchr == '?') return; /* Don't deal with these calls */
- if (num1 == 4) insert = FALSE;
- }
-
- query_terminal()
- {
- long wrcnt, w2;
- int err; char *s2;
-
- w2 = wrcnt = strlen(querystring); /* How long is the string? */
- err = FSWrite(sOut,&wrcnt,querystring); /* Respond to the query */
- }
-
- dummy()
- {
- }
-
- multi_char()
- {
- numone[0] = numtwo[0] = '0'; /* Initialize the numbers to zero */
- numone[1] = numtwo[1] = '\0';
- numptr = numone; /* Place to put the next number */
- prvchr = '\0'; /* No priv char yet */
- charflg = CF_MESC; /* Say we are in a ESC [ swequence */
- }
-
- toss_char()
- {
- charflg = CF_TOSS;
- }
-
- /*
- * Routine zeroline
- *
- * Zero (set to space) all the characters in relative line lin.
- *
- */
-
- zeroline(lin)
- int lin;
- {
- register int i;
-
- for (i=0; i<MAXCOL; i++) scr[lin][i] = ' ';
- }
-
- /*
- * Move a relative number of lines and chars. Both can be negative.
- *
- */
-
- relmove(hor,ver)
- {
- Move(hor*CHARWIDTH,ver*LINEHEIGHT);
- curcol += hor;
- abslin += ver;
- curlin = fndrel(abslin);
- }
-
- /*
- * Move to absolute position hor char and ver line.
- *
- */
-
- absmove(hor,ver)
- {
- MoveTo(hor*CHARWIDTH+LEFTMARGIN,(ver+1)*LINEHEIGHT+TOPMARGIN-LINEADJ);
- curcol = hor;
- abslin = ver;
- curlin = fndrel(ver);
- }
-
- /*
- * Find the relative line number given the absolute one.
- *
- */
-
- fndrel(linum)
- int linum;
- {
- register int i, lin;
-
- lin = toplin;
- for (i=0; i<linum; i++) lin = nxtlin[lin];
- return(lin);
- }
-
- /*
- * Find the absolute line number given the relative one.
- *
- */
-
- fndabs(linum)
- int linum;
- {
- int i, lin;
-
- lin = toplin;
- i = 0;
- while (lin != linum)
- {
- i++;
- lin = nxtlin[lin];
- }
- return(i);
- }
-
- /*
- * Find the previous relative line number from relative line linum.
- *
- */
-
- fndprv(linum)
- int linum;
- {
- int lin;
-
- lin = toplin;
- while (nxtlin[lin] != linum) lin = nxtlin[lin];
- return(lin);
- }
-
- term_redraw()
- {
- int i, lin;
-
- lin = toplin;
- for (i=0; i<MAXLIN; i++)
- {
- MoveTo(LEFTMARGIN,(i+1)*LINEHEIGHT+TOPMARGIN-LINEADJ);
- DrawString(scr[lin]);
- lin = nxtlin[lin];
- }
- MoveTo(curcol*CHARWIDTH+LEFTMARGIN,
- (abslin+1)*LINEHEIGHT+TOPMARGIN-LINEADJ);
- }
-
- init_term()
- {
- int i;
-
- for (i=0; i<MAXLIN; i++)
- {
- nxtlin[i] = i + 1; /* Tie together the linked list */
- scr[i][MAXCOL] = '\0'; /* Terminate the lines as strings */
- }
- toplin = 0; /* Initialize the top and bottom ptr */
- botlin = MAXLIN - 1;
- scrtop = toplin; /* Scrolling region equals all */
- scrbot = botlin;
- nxtlin[botlin] = -1; /* Indicate this is the end */
- }
-
- reset_term()
- {
- stop_cursor(); /* take cursor off */
- clear_screen();
- home_cursor();
- cursor_save();
-
- Invert=FALSE;
- textstyle=0;
- TextFace(0);
- TextMode(srcOr);
- TextSize(9);
-
- use_ascii = true; /* false means use graphics characters */
- keypad_app = false; /* false means don't send escape sequences */
- init_term();
- start_cursor();
- SysBeep(10);
- }
- /*
- * Support for different cursor attributes
- */
- cursor_attributes()
- { stop_cursor();
- switch(num1){
- case 0: invisible =false;
- break;
- case 1: invisible = true;
- break;
- case 2: useBlockCursor = false; /* use underline */
- break;
- case 3: useBlockCursor = true; /* use block */
- break;
- case 4: blink = false; /* don't blink */
- break;
- case 5: blink = true;
- break;
- }
- start_cursor();
- }
- /*
- Support for change keypad mode and alternate character set
- */
-
- set_ascii()
- { use_ascii = true;}
-
- set_graphics()
- { use_ascii = false; }
-
- set_keypad()
- { keypad_app = true; }
-
- reset_keypad()
- { keypad_app = false; }